package agente;

import java.util.Hashtable;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Map.Entry;

import dados.Accao;
import dados.Jogador;
import dados.Registo;
import dados.Stock;
import dados.TipoSugestao;

public class Analista {

	private Jogador jogador;
	private ArrayList<Stock> stocks;

	public Analista(Jogador jogador, ArrayList<Stock> stocks){
		this.jogador = jogador;
		this.stocks = stocks;
	}

	//int qtdsugestoes = Quantidade de sugestoes pretendidas
	public ArrayList<Sugestao> sugerirComBaseNoVolume(ArrayList<Registo> historial, int qtdsugestoes){
		ArrayList<Stock> matchstocks = matchRegistoStock(topEmpresas(historial, qtdsugestoes, 0));
		ArrayList<Stock> stocks = new ArrayList<Stock>(this.stocks);
		Integer closestValue = 0;
		for(int i = 0; i < matchstocks.size(); i++){
			for(int j = 0; j < stocks.size(); j++){
				if(matchstocks.get(i).getSigla().equals(stocks.get(j).getSigla())){
					stocks.remove(j);
				}else if(stocks.get(j).getVolume() > closestValue){
					closestValue = stocks.get(j).getVolume();
				}
			}
		}
		Stock aux = null;
		ArrayList<Sugestao> resultado = new ArrayList<Sugestao>();
		for(int i = 0; i < matchstocks.size(); i++){
			for(int j = 0; j < stocks.size(); j++){
				if(!resultado.contains(stocks.get(j).getSigla())
						&& Math.abs(matchstocks.get(i).getVolume() - stocks.get(j).getVolume())  < closestValue){
					aux = stocks.get(j);
				}
			}
			resultado.add(new Sugestao(aux, TipoSugestao.VOLUME_ANALISTA));
		}
		return resultado;
	}

	//int qtdsugestoes = Quantidade de sugestoes pretendidas
	public ArrayList<Sugestao> sugerirComBaseNasCompras(ArrayList<Registo> historial, int qtdsugestoes){
		ArrayList<Stock> matchstocks = matchRegistoStock(topEmpresas(historial, qtdsugestoes, 1));
		ArrayList<Sugestao> resultado = new ArrayList<Sugestao>();
		for(int i = 0; i < matchstocks.size(); i++){
			if(qtdsugestoes != 0){
				if(matchstocks.get(i).getVariacao() < 0){
					resultado.add(new Sugestao(matchstocks.get(i), TipoSugestao.COMPRA_ANALISTA));
					qtdsugestoes--;

				}
			}
		}
		return resultado;
	}

	//int qtdsugestoes = Quantidade de sugestoes pretendidas
	public ArrayList<Sugestao> sugerirComBaseNasVendas(ArrayList<Registo> historial, int qtdsugestoes){
		ArrayList<Stock> matchstocks = matchAccaoStock(jogador.getAccoes());
		ArrayList<Sugestao> resultado = new ArrayList<Sugestao>();
		for(int i = 0; i < matchstocks.size(); i++){
			if(qtdsugestoes != 0){
				if(matchstocks.get(i).getVariacao() > 0){
					resultado.add(new Sugestao(matchstocks.get(i), TipoSugestao.VENDA_ANALISTA));
					qtdsugestoes--;

				}
			}
		}
		return resultado;
	}

	//int qdttop = Numero de empresas que queremos no top;
	//int compra_venda = Tipo de registos a filtrar, 0 = todos, 1 = compras, 2 = vendas;
	public ArrayList<String> topEmpresas(ArrayList<Registo> historial, int qtdtop, int compra_venda){
		Hashtable<String, Integer> topempresas = new Hashtable<String, Integer>();
		for(Registo a : historial){
			if(compra_venda == 0){			
				if(topempresas.containsKey(a.getSigla())){
					topempresas.put(a.getSigla(), topempresas.get(a.getSigla()) + 1);
				}else{
					topempresas.put(a.getSigla(), 1);
				}	
			}else if(compra_venda == 1 && a.isCompra_venda()){			
				if(topempresas.containsKey(a.getSigla())){
					topempresas.put(a.getSigla(), topempresas.get(a.getSigla()) + 1);
				}else{
					topempresas.put(a.getSigla(), 1);
				}
			}else if(compra_venda == 2 && !a.isCompra_venda()){
				if(topempresas.containsKey(a.getSigla())){
					topempresas.put(a.getSigla(), topempresas.get(a.getSigla()) + 1);
				}else{
					topempresas.put(a.getSigla(), 1);
				}
			}
		}
		ArrayList<String> sugestoes = new ArrayList<String>();
		String maxKey = null;
		Integer maxValue = 0;
		if(!topempresas.isEmpty()){
			for(int i = 0; i < qtdtop; i++){
				for(Entry<String, Integer> entry : topempresas.entrySet()) {
					if(entry.getValue() > maxValue) {
						maxValue = entry.getValue();
						maxKey = entry.getKey();
					}
				}
				maxValue = 0;
				topempresas.remove(maxKey);
				sugestoes.add((String) maxKey);
			}
		}
		return sugestoes;
	}

	public ArrayList<Stock> matchRegistoStock(ArrayList<String> empresas){
		ArrayList<Stock> matchstocks = new ArrayList<Stock>();
		for(int i = 0; i < empresas.size(); i++){
			for(int j = 0; j < stocks.size(); j++){
				if(empresas.get(i).equals(stocks.get(j).getSigla())){
					matchstocks.add(stocks.get(j));
				}
			}
		}
		return matchstocks;
	}

	public ArrayList<Stock> matchAccaoStock(LinkedList<Accao> empresas){
		ArrayList<Stock> matchstocks = new ArrayList<Stock>();
		for(int i = 0; i < empresas.size(); i++){
			for(int j = 0; j < stocks.size(); j++){
				if(empresas.get(i).getSigla().equals(stocks.get(j).getSigla())){
					matchstocks.add(stocks.get(j));
				}
			}
		}
		return matchstocks;
	}

}
